﻿using LitJson2;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Windows.Forms;

namespace WebTestTools
{
    public partial class Main : Form
    {
        //线程休眠时间
        private int sleepSec = 1000;

        //用户数/线程数
        private int usersMax = 100;

        //手牌数
        private int cardMax = 1000;

        //基础url
        private string baseUrl = "http://test.kdong8.com/api/v3/";

        //测试报告文件名
        private string reportFileName = "";

        public enum httpMethod
        {
            DELETE,
            POST,
            PUT,
            GET
        }
        public Main()
        {
            InitializeComponent();
        }

        private void btnStartTest_Click(object sender, EventArgs e)
        {
            reportFileName=(cbFormal.Checked?"正式环境":"测试环境")+"测试报告"+DateTime.Now.ToString("yyyy-MM-dd");

            sleepSec = (int)(nudSleepTime.Value) * 1000;
            usersMax = (int)nudUserMaxCount.Value;
            cardMax = (int)nudCardMaxCount.Value;

            //新增首行
            CSHelper.saveTextFile(string.Format("一套流程线程休眠时间:{0},模拟用户数:{1},测试手牌数:{2}", sleepSec, usersMax, cardMax), reportFileName, "csv", true);

            CSHelper.saveTextFile(string.Format("{0},{1},{2},{3},{4},{5},{6},{7}", "日期/时间", "手牌号", "任务", "状态", "耗时(/ms)", "失败原因", "后台报错id", "报错URL"), reportFileName, "csv", true);

            // 设置线程池中处于活动的线程的最大数目
            // 设置线程池中工作者线程数量为usersMax，I/O线程数量为usersMax
            ThreadPool.SetMaxThreads(usersMax, usersMax);
            for (int i = 1; i < cardMax + 1; i++)
            {
                ThreadPool.QueueUserWorkItem(new WaitCallback(doWork), i);
            }
            appendText("所有任务完毕！");
            System.Timers.Timer timer = new System.Timers.Timer(1000);
            timer.Elapsed += timer_Elapsed;
            timer.Start();
        }

        void timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
        {
            //updateLableText(DateTime.Now.ToString());
            updateLableText(string.Format("当前线程池中线程数:{0}", getWorkingThreadsCount().ToString()));
        }

        private void doWork(object i)
        {
            string handCard = "z" + i.ToString().PadLeft(4, '0');
            appendText("准备测试，手牌号:" + handCard);
            //保存服务器返回的cookie
            CookieContainer cc = new CookieContainer();

            //计时器
            Stopwatch stopWatch = new Stopwatch();
            try
            {
                //模拟登陆
                stopWatch.Start();
                //模拟登陆=>用户名|密码=>url post or get
                try
                {
                    var loginUrl = baseUrl + "login?fc=111&rnd_rnd_rnd=1516526755514&username=testAdmin&password=1";
                    var responseLogin = HttpHelper.CreateGetHttpResponse(loginUrl, 5, null, null);
                    cc.Add(responseLogin.Cookies);
                    var responseLoginStr = HttpHelper.GetResponseString(responseLogin);
                    stopWatch.Stop();

                    var jdLogin = JsonMapper.ToObject(responseLoginStr);
                    if (jdLogin["errorCode"].ToString() == "0")
                    {
                        appendText(handCard + "登陆成功！" + " 耗时(ms):" + stopWatch.Elapsed.Milliseconds);
                        save2CSV(handCard, "登录", "成功", stopWatch.Elapsed.Milliseconds, "", "","");
                    }
                    else
                    {
                        appendText(handCard + "登陆失败！原因：" + jdLogin["errorMsg"].ToString() + "。 errorId:" + jdLogin["errorId"].ToString());
                        save2CSV(handCard, "登录", "失败", stopWatch.Elapsed.Milliseconds, jdLogin["errorMsg"].ToString(), jdLogin["errorId"].ToString(), loginUrl);
                        return;
                    }
                }
                catch (Exception e)
                {
                    appendText(handCard + " " + "登录失败！原因：" + e.Message);
                    save2CSV(handCard, "登录", "失败", stopWatch.Elapsed.Milliseconds, e.Message, "","");
                }

                //goto jump;
                //模拟刷手牌=>手牌编号
                var cardUrl = string.Format(baseUrl + "cards/getByCode?code={0}&used=false&fromSite=612198576243606528&fc=111", handCard);
                doRequestTask("获取手牌信息", cardUrl, null, cc, stopWatch, handCard,httpMethod.GET.ToString());

                //模拟模拟卖票
                var saleTicketUrl = baseUrl + "posBills?fromSite=612198576243606528&fc=111&rnd_rnd_rnd=1516584365483";
                var jsonStr = "{\"creatorSiteId\":\"612198576243606528\",\"creatorSiteName\":\"雪服\",\"customer\":null,\"customerCategoryId\":\"\",\"customerCardNo\":\"\",\"customerCategoryName\":\"\",\"customerAge\":0,\"customerFullName\":\"\",\"customerMobilePhone\":\"\",\"customerSex\":\"\",\"deposit\":\"500\",\"details\":[{\"accountIncomeCategory\":{\"value\":\"\"},\"accountIncomeId\":\"0\",\"accountIncomeName\":\"\",\"addedMinutes\":0,\"adminCardCode\":\"\",\"adminCardLogin\":{\"id\":\"0\"},\"adminCardName\":\"\",\"amount\":\"50\",\"cardNo\":\"z0001\",\"category\":{\"value\":\"gym\"},\"costAmount\":0,\"costPrice\":0,\"creatorSiteGroupId\":\"612198700738937856\",\"creatorSiteGroupName\":\"总台\",\"creatorSiteId\":\"612198576243606528\",\"creatorSiteName\":\"雪服\",\"deposit\":\"500\",\"discountAmount\":\"0\",\"discountRate\":0,\"endTime\":\"\",\"gymKind\":{\"id\":\"616875628410438656\",\"version\":\"1\",\"createTime\":\"2017-10-24 14:59\",\"updateTime\":\"2017-10-24 14:59\",\"creatorAppId\":\"544323167695406081\",\"updaterAppId\":\"544323167695406081\",\"creatorName\":\"testAdmin\",\"updaterName\":\"testAdmin\",\"company\":{\"id\":\"314316463546565632\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"entityNo\":null,\"cname\":null,\"ename\":null,\"account\":null,\"apiUrl\":null,\"year\":0,\"visibleInDong8\":true,\"name\":null,\"tenantType\":{\"value\":\"company\",\"desc\":\"公司\"},\"timeStamp\":null,\"idString\":\"314316463546565632\",\"shortId\":\"CgFUNGUwvY\"},\"club\":{\"id\":\"111\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"clubCode\":null,\"clubName\":null,\"clubEnName\":null,\"company\":null,\"account\":null,\"address\":null,\"description\":null,\"lat\":null,\"lng\":null,\"phone\":null,\"price\":null,\"workTime\":null,\"type\":null,\"province\":null,\"cityStr\":null,\"city\":null,\"img\":null,\"service\":null,\"fclubCode\":null,\"flag\":0,\"hot\":0,\"attribute\":null,\"updateBy\":\"0\",\"hasSubidy\":false,\"salesMan\":null,\"contactName\":null,\"contactPhone\":null,\"contactEmail\":null,\"financeName\":null,\"financePhone\":null,\"financeEmail\":null,\"adminName\":null,\"adminPwd\":null,\"pingxxAppId\":null,\"pingxxLiveKey\":null,\"pingxxTestKey\":null,\"settings\":[],\"name\":null,\"tenantType\":{\"value\":\"club\",\"desc\":\"场馆\"},\"projects\":null,\"setting\":null,\"timeStamp\":null,\"idString\":\"111\",\"shortId\":\"1T\"},\"clubName\":\"测试场馆\",\"name\":\"滑雪\",\"project\":{\"id\":\"616875368476836864\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"company\":null,\"club\":null,\"clubName\":null,\"name\":null,\"enable\":true,\"timeStamp\":null,\"idString\":\"616875368476836864\",\"shortId\":\"1ccgkUevjpx\"},\"saleType\":{\"value\":1,\"desc\":\"门票售卖\"},\"settleType\":{\"value\":1,\"desc\":\"开场后结账\"},\"enable\":true,\"areaCount\":1,\"maxCountByArea\":20,\"periodSize\":0,\"autoClear\":true,\"canBooking\":true,\"startTime\":8,\"endTime\":22,\"breakStartTime\":null,\"breakEndTime\":null,\"gymItems\":[],\"gymPeriods\":[],\"timeStamp\":\"2017-10-24 14:59\",\"idString\":\"616875628410438656\",\"shortId\":\"1ccgt3PQeDb\"},\"identityCode\":\"z0001\",\"identityType\":{\"value\":\"card\"},\"incomeFlag\":true,\"item\":{\"id\":\"647335545671779328\",\"category\":{\"value\":\"gym\"}},\"itemCode\":\"\",\"itemName\":\"滑雪后结账票\",\"itemTopCategoryId\":\"616875368476836864\",\"number\":\"1\",\"paidAmount\":0,\"paidMinutes\":10,\"startEquipmentId\":0,\"startEquipmentName\":\"\",\"posBill\":{\"id\":\"0\"},\"prepay\":\"300\",\"price\":\"50\",\"remark\":\"\",\"returnNumber\":\"0\",\"returned\":false,\"settleSiteId\":\"0\",\"settleSiteName\":\"\",\"settleStatus\":{\"value\":\"0\"},\"settleTime\":\"\",\"settleUserId\":\"0\",\"settleUserName\":\"\",\"startTime\":\"\",\"stockType\":false,\"teacher\":{\"id\":\"0\"},\"timeoutFlag\":false,\"teacherName\":\"\",\"timeBeginType\":{\"value\":\"2\"},\"timeoutSetting\":null,\"userPaidService\":null,\"userPaidServiceName\":\"\",\"wareHouseId\":\"0\",\"wareHouseName\":\"\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true,\"gymItemId\":\"\",\"gymItemCode\":\"\"}],\"incomdeCategory\":{\"value\":\"gym\"},\"order\":null,\"orderCode\":\"\",\"payAmount\":\"0\",\"payerCardNo\":\"z0001\",\"payerIdentityCode\":\"z0001\",\"payerIdentityType\":{\"value\":\"card\"},\"payments\":[],\"persons\":[],\"prepay\":\"300\",\"saleType\":{\"value\":\"1\"},\"settleAmount\":\"50\",\"settleSiteId\":\"0\",\"settleSiteName\":\"\",\"settleStatus\":{\"value\":\"3\"},\"settleTime\":\"\",\"settleType\":{\"value\":\"1\"},\"settleUserId\":\"0\",\"settleUserName\":\"\",\"code\":\"\",\"name\":\"\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true,\"gymItemCode\":\"\",\"gymItemId\":\"\"}";
                if (saleTicketUrl.Contains("www."))
                {
                    jsonStr = "{\"creatorSiteId\":\"612198576243606528\",\"creatorSiteName\":\"雪服\",\"customer\":null,\"customerCategoryId\":\"\",\"customerCardNo\":\"\",\"customerCategoryName\":\"\",\"customerAge\":0,\"customerFullName\":\"\",\"customerMobilePhone\":\"\",\"customerSex\":\"\",\"deposit\":\"500\",\"details\":[{\"accountIncomeCategory\":{\"value\":\"\"},\"accountIncomeId\":\"0\",\"accountIncomeName\":\"\",\"addedMinutes\":0,\"adminCardCode\":\"\",\"adminCardLogin\":{\"id\":\"0\"},\"adminCardName\":\"\",\"amount\":\"50\",\"cardNo\":\"z0001\",\"category\":{\"value\":\"gym\"},\"costAmount\":0,\"costPrice\":0,\"creatorSiteGroupId\":\"612198700738937856\",\"creatorSiteGroupName\":\"总台\",\"creatorSiteId\":\"612198576243606528\",\"creatorSiteName\":\"雪服\",\"deposit\":\"500\",\"discountAmount\":\"0\",\"discountRate\":0,\"endTime\":\"\",\"gymKind\":{\"id\":\"616875628410438656\",\"version\":\"1\",\"createTime\":\"2017-10-24 14:59\",\"updateTime\":\"2017-10-24 14:59\",\"creatorAppId\":\"544323167695406081\",\"updaterAppId\":\"544323167695406081\",\"creatorName\":\"testAdmin\",\"updaterName\":\"testAdmin\",\"company\":{\"id\":\"314316463546565632\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"entityNo\":null,\"cname\":null,\"ename\":null,\"account\":null,\"apiUrl\":null,\"year\":0,\"visibleInDong8\":true,\"name\":null,\"tenantType\":{\"value\":\"company\",\"desc\":\"公司\"},\"timeStamp\":null,\"idString\":\"314316463546565632\",\"shortId\":\"CgFUNGUwvY\"},\"club\":{\"id\":\"111\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"clubCode\":null,\"clubName\":null,\"clubEnName\":null,\"company\":null,\"account\":null,\"address\":null,\"description\":null,\"lat\":null,\"lng\":null,\"phone\":null,\"price\":null,\"workTime\":null,\"type\":null,\"province\":null,\"cityStr\":null,\"city\":null,\"img\":null,\"service\":null,\"fclubCode\":null,\"flag\":0,\"hot\":0,\"attribute\":null,\"updateBy\":\"0\",\"hasSubidy\":false,\"salesMan\":null,\"contactName\":null,\"contactPhone\":null,\"contactEmail\":null,\"financeName\":null,\"financePhone\":null,\"financeEmail\":null,\"adminName\":null,\"adminPwd\":null,\"pingxxAppId\":null,\"pingxxLiveKey\":null,\"pingxxTestKey\":null,\"settings\":[],\"name\":null,\"projects\":null,\"setting\":null,\"tenantType\":{\"value\":\"club\",\"desc\":\"场馆\"},\"timeStamp\":null,\"idString\":\"111\",\"shortId\":\"1T\"},\"clubName\":\"测试场馆\",\"name\":\"滑雪\",\"project\":{\"id\":\"616875368476836864\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"company\":null,\"club\":null,\"clubName\":null,\"name\":null,\"enable\":true,\"timeStamp\":null,\"idString\":\"616875368476836864\",\"shortId\":\"1ccgkUevjpx\"},\"saleType\":{\"value\":1,\"desc\":\"门票售卖\"},\"settleType\":{\"value\":1,\"desc\":\"开场后结账\"},\"enable\":true,\"areaCount\":1,\"maxCountByArea\":20,\"periodSize\":0,\"autoClear\":true,\"canBooking\":true,\"startTime\":8,\"endTime\":22,\"breakStartTime\":null,\"breakEndTime\":null,\"gymItems\":[],\"gymPeriods\":[],\"timeStamp\":\"2017-10-24 14:59\",\"idString\":\"616875628410438656\",\"shortId\":\"1ccgt3PQeDb\"},\"identityCode\":\"z0001\",\"identityType\":{\"value\":\"card\"},\"incomeFlag\":true,\"item\":{\"id\":\"649595749058741248\",\"category\":{\"value\":\"gym\"}},\"itemCode\":\"\",\"itemName\":\"滑雪后结账票\",\"itemTopCategoryId\":\"616875368476836864\",\"number\":\"1\",\"paidAmount\":0,\"paidMinutes\":10,\"startEquipmentId\":0,\"startEquipmentName\":\"\",\"posBill\":{\"id\":\"0\"},\"prepay\":\"300\",\"price\":\"50\",\"remark\":\"\",\"returnNumber\":\"0\",\"returned\":false,\"settleSiteId\":\"0\",\"settleSiteName\":\"\",\"settleStatus\":{\"value\":\"0\"},\"settleTime\":\"\",\"settleUserId\":\"0\",\"settleUserName\":\"\",\"startTime\":\"\",\"stockType\":false,\"teacher\":{\"id\":\"0\"},\"timeoutFlag\":false,\"teacherName\":\"\",\"timeBeginType\":{\"value\":2,\"desc\":\"购票开始计时\"},\"timeoutSetting\":{\"id\":\"616880103099466752\",\"version\":\"3\",\"createTime\":\"2017-10-24 15:16\",\"updateTime\":\"2017-12-03 22:42\",\"creatorAppId\":\"544323167695406081\",\"updaterAppId\":\"544323167695406081\",\"creatorName\":\"testAdmin\",\"updaterName\":\"testAdmin\",\"company\":{\"id\":\"314316463546565632\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"entityNo\":null,\"cname\":null,\"ename\":null,\"account\":null,\"apiUrl\":null,\"year\":0,\"visibleInDong8\":true,\"name\":null,\"tenantType\":{\"value\":\"company\",\"desc\":\"公司\"},\"timeStamp\":null,\"idString\":\"314316463546565632\",\"shortId\":\"CgFUNGUwvY\"},\"club\":{\"id\":\"111\",\"version\":\"1\",\"createTime\":null,\"updateTime\":null,\"creatorAppId\":\"0\",\"updaterAppId\":\"0\",\"creatorName\":null,\"updaterName\":null,\"clubCode\":null,\"clubName\":null,\"clubEnName\":null,\"company\":null,\"account\":null,\"address\":null,\"description\":null,\"lat\":null,\"lng\":null,\"phone\":null,\"price\":null,\"workTime\":null,\"type\":null,\"province\":null,\"cityStr\":null,\"city\":null,\"img\":null,\"service\":null,\"fclubCode\":null,\"flag\":0,\"hot\":0,\"attribute\":null,\"updateBy\":\"0\",\"hasSubidy\":false,\"salesMan\":null,\"contactName\":null,\"contactPhone\":null,\"contactEmail\":null,\"financeName\":null,\"financePhone\":null,\"financeEmail\":null,\"adminName\":null,\"adminPwd\":null,\"pingxxAppId\":null,\"pingxxLiveKey\":null,\"pingxxTestKey\":null,\"settings\":[],\"name\":null,\"projects\":null,\"setting\":null,\"tenantType\":{\"value\":\"club\",\"desc\":\"场馆\"},\"timeStamp\":null,\"idString\":\"111\",\"shortId\":\"1T\"},\"clubName\":\"测试场馆\",\"name\":\"滑雪超时方案\",\"timeBeginType\":{\"value\":2,\"desc\":\"购票开始计时\"},\"product\":null,\"bufferTime\":20,\"firstSeconds\":30,\"firstAmount\":50,\"afterSeconds\":5,\"afterAmount\":5,\"maxAfterCount\":0,\"remark\":\"\",\"timeStamp\":\"2017-12-03 22:42\",\"idString\":\"616880103099466752\",\"shortId\":\"1ccif8N0kQ4\"},\"userPaidService\":null,\"userPaidServiceName\":\"\",\"wareHouseId\":\"0\",\"wareHouseName\":\"\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true,\"gymItemId\":\"\",\"gymItemCode\":\"\"}],\"incomdeCategory\":{\"value\":\"gym\"},\"order\":null,\"orderCode\":\"\",\"payAmount\":\"0\",\"payerCardNo\":\"z0001\",\"payerIdentityCode\":\"z0001\",\"payerIdentityType\":{\"value\":\"card\"},\"payments\":[],\"persons\":[],\"prepay\":\"300\",\"saleType\":{\"value\":\"1\"},\"settleAmount\":\"50\",\"settleSiteId\":\"0\",\"settleSiteName\":\"\",\"settleStatus\":{\"value\":\"3\"},\"settleTime\":\"\",\"settleType\":{\"value\":\"1\"},\"settleUserId\":\"0\",\"settleUserName\":\"\",\"code\":\"\",\"name\":\"\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true,\"gymItemCode\":\"\",\"gymItemId\":\"\"}";
                }
                jsonStr = jsonStr.Replace("z0001", handCard);
                string billcode = doRequestTask("来场卖票", saleTicketUrl, jsonStr, cc, stopWatch, handCard, httpMethod.POST.ToString());

                //缴纳押金
                var payDepositURL = baseUrl + "posBills/pay?fromSite=612198576243606528&fc=111&rnd_rnd_rnd=1516587104971";
                var payJsonStr = "{\"posBillId\":\"{0}\",\"settle\":false,\"cardNo\":\"\",\"identityCode\":\"\",\"identityType\":{\"value\":\"\"},\"adminLoginToken\":\"\",\"payments\":[{\"paymentType\":{\"id\":\"619064811208049664\"},\"paymentTypeName\":\"现金\",\"paymentTypeCategory\":{\"value\":1,\"desc\":\"现金\"},\"amount\":\"400\",\"cardNo\":\"\",\"discountAmount\":0,\"identityCode\":\"\",\"identityType\":{\"value\":\"card\"},\"payAmount\":\"400\",\"posBill\":{\"id\":\"0\"},\"site\":{\"id\":\"612198576243606528\"},\"siteName\":\"雪服\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true},{\"paymentType\":{\"id\":\"619064843445470208\"},\"paymentTypeName\":\"支付宝\",\"paymentTypeCategory\":{\"value\":8,\"desc\":\"支付宝\"},\"amount\":\"400\",\"cardNo\":\"\",\"discountAmount\":0,\"identityCode\":\"\",\"identityType\":{\"value\":\"card\"},\"payAmount\":\"400\",\"posBill\":{\"id\":\"0\"},\"site\":{\"id\":\"612198576243606528\"},\"siteName\":\"雪服\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true}]}";
                payJsonStr = payJsonStr.Replace("{0}", billcode);

                doRequestTask("缴纳押金", payDepositURL, payJsonStr, cc, stopWatch, handCard, httpMethod.POST.ToString());

            jump:
                //模拟结账
                //查询手牌账单号
                var settleInfoUrl = string.Format(baseUrl + "posBills/settleInfo?code={0}&fromSite=612198576243606528&fc=111&rnd_rnd_rnd=1516619795131", handCard);
                billcode = doRequestTask("根据手牌获取账单", settleInfoUrl, null, cc, stopWatch, handCard,httpMethod.GET.ToString());

                if (billcode == string.Empty) return;

                //根据手牌号和账单号结账
                var settleJson = "{\"identity\":{\"cardNo\":\"z0001\",\"code\":\"z0001\",\"type\":{\"value\":\"card\",\"desc\":\"手牌\"}},\"posBill\":{\"id\":\"{0}\"},\"endTime\":\"2018-01-22 10:44\"}";
                settleJson = settleJson.Replace("z0001", handCard);
                settleJson = settleJson.Replace("{0}", billcode);
                doRequestTask("来场结账",
                baseUrl + "posBills/settle?fromSite=612198576243606528&fc=111&rnd_rnd_rnd=1516589099228",
                settleJson, cc, stopWatch, handCard, httpMethod.PUT.ToString());

                //结账付款
                var settlePayJson = "{\"posBillId\":\"{0}\",\"settle\":true,\"cardNo\":\"z0001\",\"identityCode\":\"z0001\",\"identityType\":{\"value\":\"card\"},\"adminLoginToken\":\"\",\"payments\":[{\"paymentType\":{\"id\":\"619064811208049664\"},\"paymentTypeName\":\"现金\",\"paymentTypeCategory\":{\"value\":1,\"desc\":\"现金\"},\"amount\":\"-750\",\"cardNo\":\"\",\"discountAmount\":0,\"identityCode\":\"\",\"identityType\":{\"value\":\"card\"},\"payAmount\":\"-750\",\"posBill\":{\"id\":\"0\"},\"site\":{\"id\":\"612198576243606528\"},\"siteName\":\"雪服\",\"club\":{\"id\":\"0\"},\"clubName\":\"\",\"company\":{\"id\":\"0\"},\"id\":\"0\",\"editMode\":true,\"isNew\":true}]}";
                settlePayJson = settlePayJson.Replace("z0001", handCard);
                settlePayJson = settlePayJson.Replace("{0}", billcode);
                doRequestTask("结账付款",
                   baseUrl + "posBills/pay?fromSite=612198576243606528&fc=111&rnd_rnd_rnd=1516589116405",
                   settlePayJson, cc, stopWatch, handCard, httpMethod.POST.ToString());

                //如果要测试脚本的话
                if (txtCSVPath.Text != string.Empty && cbExecCSV.Checked)
                {
                    DateTime dt_read_txt = DateTime.Now;
                    linecount = 0;
                    for (int j = 0; j < path.Length; j++)
                    {
                        //using (StreamReader sr = new StreamReader(path[j], System.Text.Encoding.GetEncoding("UTF-8")))
                        using (StreamReader sr = new StreamReader(path[j], System.Text.Encoding.Default))
                        {
                            string line = string.Empty;
                            while ((line = sr.ReadLine()) != null)
                            {
                                //如果读出一行不是空字符串
                                if (line.Trim() != "")
                                {

                                    linecount++;
                                    if (linecount == 1 && true)
                                    {
                                        //第一行遗弃
                                        continue;
                                    }
                                    //当遇到内容带有,的时候，就需要正则去匹配了
                                    Regex CSVParser = new Regex(",(?=(?:[^\"]*\"[^\"]*\")*(?![^\"]*\"))");
                                    var arr = CSVParser.Split(line);
                                    //0功能>1URL>2请求方法>3请求body
                                    var postJson=arr[3].Replace("\"\"", "\"");
                                    if (postJson.Trim() != string.Empty)
                                    {
                                        postJson = postJson.Substring(1, postJson.Length - 1);
                                    }
                                    doRequestTask("【" + arr[0] + "】",
                                        arr[1].Replace("http://test.kdong8.com/api/v3/", baseUrl),postJson , cc, stopWatch, handCard, arr[2]);
                                }
                            }


                        }
                    }
                }
            }
            catch (Exception ex)
            {
                appendText(ex.Message + "\n\r" + ex.StackTrace);

            }
            finally
            {
                //线程休眠一秒
                Thread.Sleep(sleepSec);
            }
        }

        int MaxWorkerThreads, miot, AvailableWorkerThreads, aiot;
        private int getWorkingThreadsCount()
        {
            //获得最大的线程数量  
            ThreadPool.GetMaxThreads(out MaxWorkerThreads, out miot);

            //获得可用的线程数量  
            ThreadPool.GetAvailableThreads(out AvailableWorkerThreads, out aiot);
            //AvailableWorkerThreads = aiot = 0;

            //返回线程池中活动的线程数  
            return MaxWorkerThreads - AvailableWorkerThreads;
        }

        private void updateLableText(string text)
        {
            Action<string> actionDelegate = (x) =>
            {
                lblThreadCount.Text = text;
            };
            this.lblThreadCount.Invoke(actionDelegate, text);
        }

        public string lastLogText = "";
        /// <summary>
        /// 添加到日志
        /// </summary>
        /// <param name="log">日志信息</param>
        private void appendText(string log, bool save = true)
        {
            Action<string> actionDelegate = (x) =>
            {
                if (this.richTextBox1.Text.Length > 20000)
                {
                    this.richTextBox1.Text = this.richTextBox1.Text.Substring(20000, this.richTextBox1.Text.Length - 20000);
                }
                this.richTextBox1.AppendText(DateTime.Now.ToString() + ":" + log);
                richTextBox1.AppendText(System.Environment.NewLine);
                this.richTextBox1.ScrollToCaret();
            };
            this.richTextBox1.Invoke(actionDelegate, log);
            //CSHelper.saveErrLog(log, "report");
        }

        private void save2CSV(string card, string taskName, string flag, int sec, string reason, string errorId, string url)
        {
            CSHelper.saveTextFile(string.Format("{0},{1},{2},{3},{4},{5},{6},{7}", DateTime.Now.ToString(), card, taskName, flag, sec, reason, errorId, url), reportFileName, "csv", true);
        }
        /// <summary>
        /// 处理请求任务
        /// </summary>
        /// <param name="taskName">任务名</param>
        /// <param name="url">请求地址</param>
        /// <param name="postJson">post参数</param>
        /// <param name="cc">cookie</param>
        /// <param name="stopWatch">计时器</param>
        /// <returns>rtnData</returns>
        private string doRequestTask(string taskName, string url, string postJson, CookieContainer cc, Stopwatch stopWatch, string handCard,string httpMethod)
        {
            stopWatch = new Stopwatch();
            var rtnData = "";
            stopWatch.Start();
            var responseStr = "";
            try
            {
                //if (taskName == "来场结账")
                //{
                //    responseStr = HttpHelper.GetResponseString(HttpHelper.CreatePutHttpResponse(url, postJson, cc));
                //}
                //else if (taskName == "获取手牌信息" || taskName == "根据手牌获取账单" || taskName.StartsWith("【"))
                //{
                //    responseStr = HttpHelper.GetResponseString(HttpHelper.CreateGetHttpResponse(url, 5, null, cc));
                //}
                //else
                //{
                //    responseStr = HttpHelper.GetResponseString(HttpHelper.CreatePostHttpResponse(url, postJson, cc));
                //}
                switch (httpMethod.ToLower())
                {
                    case "get": responseStr = HttpHelper.GetResponseString(HttpHelper.CreateGetHttpResponse(url, 5, null, cc)); break;
                    case "post": responseStr = HttpHelper.GetResponseString(HttpHelper.CreatePostHttpResponse(url, postJson, cc)); break;
                    case "delete": responseStr = HttpHelper.GetResponseString(HttpHelper.CreateDeleteHttpResponse(url, postJson, cc)); break;
                    case "put": responseStr = HttpHelper.GetResponseString(HttpHelper.CreatePutHttpResponse(url, postJson, cc)); break;
                    default: responseStr = ""; break;
                }

                var jd = JsonMapper.ToObject(responseStr);
                if (responseStr != string.Empty)
                {
                    stopWatch.Stop();
                }
                else
                {
                    appendText("惨了，居然没有进来！");
                    return "";
                }
                if (jd["errorCode"].ToString() == "0")
                {
                    if (taskName == "来场卖票")
                    {
                        rtnData = jd["data"]["id"].ToString();
                    }
                    if (taskName == "根据手牌获取账单")
                    {
                        rtnData = jd["data"]["posBill"]["id"].ToString();
                    }
                    appendText(handCard + " " + taskName + "成功！" + " 耗时(ms):" + stopWatch.Elapsed.Milliseconds);
                    save2CSV(handCard, taskName, "成功", stopWatch.Elapsed.Milliseconds, "", "","");
                }
                else
                {
                    appendText(handCard + " " + taskName + "失败！原因：" + jd["errorMsg"].ToString() + "。 errorId:" + jd["errorId"].ToString());
                    save2CSV(handCard, taskName, "失败", stopWatch.Elapsed.Milliseconds, jd["errorMsg"].ToString(), jd["errorId"].ToString(), url);
                }

            }
            catch (Exception ex)
            {
                if (stopWatch.IsRunning)
                {
                    stopWatch.Stop();
                }
                appendText(handCard + " " + taskName + "失败！原因：" + ex.Message);
                save2CSV(handCard, taskName, "失败", stopWatch.Elapsed.Milliseconds, ex.Message, "","");
            }
            finally
            {

            }
            return rtnData;
        }

        private void cbFormal_CheckedChanged(object sender, EventArgs e)
        {
            if (cbFormal.Checked)
            {
                baseUrl = "http://www.kdong8.com/api/v3/";
            }
            else
            {
                baseUrl = "http://test.kdong8.com/api/v3/";
            }
        }

        private void btnViewRpt_Click(object sender, EventArgs e)
        {
            if (File.Exists(Application.StartupPath + "\\" + reportFileName + ".csv"))
            {
                Process.Start(Application.StartupPath + "\\" + reportFileName + ".csv");
            }
            else
            {
                MessageBox.Show("测试报告不存在，请先启动测试！");
            }
        }

        string[] path = null;
        public long linecount = 0;
        private void btnChooseCSV_Click(object sender, EventArgs e)
        {
            OpenFileDialog ofd = new OpenFileDialog();
            ofd.Title = "打开";
            ofd.Filter = "所有文件|*.csv";
            ofd.Multiselect = true;
            ofd.InitialDirectory = Application.StartupPath;
            if (ofd.ShowDialog() == DialogResult.OK)
            {
                path = ofd.FileNames;
                txtCSVPath.Text = ofd.FileNames[0];
            }
            if (path == null)
            {
                return;
            }
        }

        private void Main_Load(object sender, EventArgs e)
        {
            reportFileName = (cbFormal.Checked ? "正式环境" : "测试环境") + "测试报告" + DateTime.Now.ToString("yyyy-MM-dd");
        }
    }
}
